package com.eastfair.venuebooking.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.util.StrUtil;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.eastfair.auth.api.UserAccountServiceFeign;
import com.eastfair.auth.dto.UserAccountDto;
import com.eastfair.auth.vo.UserAccountVo;
import com.eastfair.core.context.ContextUtil;
import com.eastfair.core.exception.BizException;
import com.eastfair.venuebooking.dao.SpaceCategoryMapper;
import com.eastfair.venuebooking.dao.SpaceMapper;
import com.eastfair.venuebooking.dto.SpaceCategoryPageQuery;
import com.eastfair.venuebooking.dto.SpaceCategorySaveDTO;
import com.eastfair.venuebooking.dto.SpaceCategoryUpdateDTO;
import com.eastfair.venuebooking.entity.Space;
import com.eastfair.venuebooking.entity.SpaceCategory;
import com.eastfair.venuebooking.exceptioncode.VenueBookingExceptionCode;
import com.eastfair.venuebooking.service.SpaceCategoryService;
import com.eastfair.boot.service.SuperServiceImpl;

import com.eastfair.venuebooking.vo.SpaceCategoryVO;
import com.eastfair.venueservice.entity.ExhibitionServiceProvider;
import com.google.common.collect.Maps;
import io.swagger.annotations.ApiModelProperty;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.logging.log4j.util.Strings;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import com.baomidou.mybatisplus.extension.toolkit.SqlHelper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.eastfair.constant.BusinessConstant;
import com.eastfair.core.base.R;

import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.function.Function;
import java.util.stream.Collectors;

//import com.baomidou.dynamic.datasource.annotation.DS;
import org.springframework.transaction.annotation.Transactional;

/**
 * <p>
 * 业务实现类
 * 场地分类表
 * </p>
 *
 * @author linan
 * @date 2022-06-08
 */
@Slf4j
@Service
//@DS("#thread.tenant")
public class SpaceCategoryServiceImpl extends SuperServiceImpl<SpaceCategoryMapper, SpaceCategory> implements SpaceCategoryService {

    @Autowired
    private SpaceCategoryMapper spaceCategoryMapper;
    @Autowired
    private SpaceMapper spaceMapper;
    @Autowired
    private UserAccountServiceFeign userAccountServiceFeign;


    /**
     * 处理逻辑删除相关处理
     *
     * @param modelList 实体
     * @return 是否成功
     */
    @Override
    protected R<Boolean> handlerRemoveByIdsOfLogic(Collection<SpaceCategory> modelList) {
        modelList.stream().forEach(s -> {
            s.setIsDeleted(BusinessConstant.YES);
        });
        // TODO: 2021/10/29 这里需要操作其他业务，如清空角色等
        return R.successDef();
    }


    @Override
    protected R<Boolean> handlerSave(SpaceCategory model) {
        model.setProjectId(ContextUtil.getProjectId());
        model.setSubsystemId(ContextUtil.getSubSystemId());
        model.setTenantId(ContextUtil.getTenantId());
        return R.successDef();
    }


    /**
     * 查询展厅分类列表
     *
     * @param spaceCategoryPageQuery
     * @return
     */
    @Override
    public List<SpaceCategoryVO> querySpaceCategoryList(SpaceCategoryPageQuery spaceCategoryPageQuery) {
        log.info("SpaceCategoryServiceImpl +++++ querySpaceCategoryList - 查询展厅分类列表 params={}", JSONObject.toJSON(spaceCategoryPageQuery));
        List<SpaceCategoryVO> spaceCategoryVOList = spaceCategoryMapper.selectSpaceCategoryList(spaceCategoryPageQuery);
        QueryWrapper<SpaceCategory> queryWrapper = new QueryWrapper<>();
        queryWrapper.lambda()
                .eq(SpaceCategory::getIsDeleted, BusinessConstant.DELETE_NO)
                .eq(SpaceCategory::getIsEnabled, BusinessConstant.ENABLE_YES);
        List<SpaceCategory> list = this.list(queryWrapper);
        List<Long> userIds = list.stream().map(SpaceCategory::getCreatedBy).collect(Collectors.toList());
        UserAccountDto userAccountDto = new UserAccountDto();
        userAccountDto.setUserIds(userIds);
        //获取人员信息
        R<List<UserAccountVo>> listR = userAccountServiceFeign.querySimpleByIds(userAccountDto);
        //把人员信息转成map
        Map<Long, UserAccountVo> userMap= Maps.newHashMap();
        if(Objects.nonNull(listR) && CollectionUtils.isNotEmpty(listR.getData())){
           userMap = listR.getData().stream().collect(Collectors.toMap(UserAccountVo::getId, Function.identity()));
            if (Objects.nonNull(spaceCategoryVOList) && spaceCategoryVOList.size() > 0) {
                Map<Long, UserAccountVo> finalUserMap = userMap;
                spaceCategoryVOList.forEach((s) -> {
                    UserAccountVo userAccountVo = finalUserMap.get(s.getCreatedBy());
                    if (Objects.nonNull(userAccountVo)) {
                        s.setCreatedName(userAccountVo.getRealName());
                    }
                    //遍历子集分类
                    s.getChildren().forEach((s1) -> {
                        UserAccountVo userAccount = finalUserMap.get(s1.getCreatedBy());
                        if (Objects.nonNull(userAccount)) {
                            s1.setCreatedName(userAccount.getRealName());
                        }
                    });
                });
            }
        }
        return spaceCategoryVOList;
    }

    @Override
    public List<SpaceCategory> listByCategoryNames(List<String> spaceCategoryNames) {
        log.info("listBySpaceName - 展厅分类名称批量查询展厅分类, spaceCategoryNames={}", spaceCategoryNames);
        QueryWrapper<SpaceCategory> queryWrapper = new QueryWrapper<>();
        queryWrapper
                .lambda()
                .eq(SpaceCategory::getIsDeleted, BusinessConstant.DELETE_NO)
                .in(spaceCategoryNames != null && !spaceCategoryNames.isEmpty(), SpaceCategory::getCategoryName, spaceCategoryNames)
        ;
        return list(queryWrapper);
    }

    /**
     * 添加展厅分类
     *
     * @param spaceCategorySaveDTO
     * @return
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public Boolean saveSpaceCategoryInfo(SpaceCategorySaveDTO spaceCategorySaveDTO) {
        log.info("SpaceCategoryServiceImpl +++++ saveSpaceCategoryInfo - 添加展厅分类 params={}", JSONObject.toJSON(spaceCategorySaveDTO));
        List<SpaceCategory> list= this.list(new QueryWrapper<SpaceCategory>().lambda()
                .eq(SpaceCategory::getIsDeleted, BusinessConstant.DELETE_NO)
                .eq(Strings.isNotBlank(spaceCategorySaveDTO.getCategoryName()), SpaceCategory::getCategoryName, spaceCategorySaveDTO.getCategoryName()));
        //展厅分类名称查重
        if (Objects.nonNull(list) && list.size() > 0) {
            throw BizException.wrap(VenueBookingExceptionCode.SPC_EXISTENCE);
        }
        SpaceCategory spaceCategory = BeanUtil.toBean(spaceCategorySaveDTO, SpaceCategory.class);
        R<UserAccountVo> r = userAccountServiceFeign.findSimpleById(ContextUtil.getUserId());
        Boolean save = this.save(spaceCategory);

        if (Boolean.TRUE.equals(save)) {
            log.info("SpaceCategoryServiceImpl +++++ saveSpaceCategoryInfo --》》》》 添加展厅分类成功");
        }
        return save;
    }

    /**
     * 修改展厅分类
     *
     * @param spaceCategoryUpdateDTO
     * @return
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public Boolean updateSpaceCategoryInfo(SpaceCategoryUpdateDTO spaceCategoryUpdateDTO) {
        log.info("SpaceCategoryServiceImpl +++++ updateSpaceCategoryInfo - 修改展厅分类 params={}", JSONObject.toJSON(spaceCategoryUpdateDTO));
        List<SpaceCategory> list= this.list(new QueryWrapper<SpaceCategory>().lambda()
                .eq(SpaceCategory::getIsDeleted, BusinessConstant.DELETE_NO)
                .eq(Strings.isNotBlank(spaceCategoryUpdateDTO.getCategoryName()), SpaceCategory::getCategoryName, spaceCategoryUpdateDTO.getCategoryName()));
        //展厅分类名称查重
        //判断是否是自己
        if (Objects.nonNull(list) && list.size()>0 && Objects.nonNull(list.get(0)) && list.get(0).getId().longValue()!=spaceCategoryUpdateDTO.getId().longValue()) {
            throw BizException.wrap(VenueBookingExceptionCode.SPC_EXISTENCE);
        }
        //修改分类时查询是否被展厅引用
        QueryWrapper<Space> queryWrapper = new QueryWrapper<>();
        queryWrapper.lambda()
                .eq(Objects.nonNull(spaceCategoryUpdateDTO.getId()),
                        Space::getSpaceCategoryId, spaceCategoryUpdateDTO.getId())
                .eq(Space::getIsDeleted, BusinessConstant.DELETE_NO);
        List<Space> spaceList = spaceMapper.selectList(queryWrapper);
        if (Objects.nonNull(spaceList) && spaceList.size() > 0) {
            throw BizException.wrap(VenueBookingExceptionCode.SP_NOT_UPDATE);
        }
        SpaceCategory spaceCategory = BeanUtil.toBean(spaceCategoryUpdateDTO, SpaceCategory.class);
        Boolean update = this.updateById(spaceCategory);
        if (Boolean.TRUE.equals(update)) {
            log.info("SpaceCategoryServiceImpl +++++ updateSpaceCategoryInfo -》》》》 修改展厅分类成功");
        }
        return update;
    }


    /**
     * 删除展厅分类
     *
     * @param id
     * @return
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public Boolean delSpaceCategoryInfoById(Long id) {
        log.info("SpaceCategoryServiceImpl +++++ delSpaceCategoryInfoById - 删除展厅分类 params={}", id);
        //删除分类时查询是否被展厅引用
        List<Space> spaceList = getSpaceList(id);
        if (Objects.nonNull(spaceList) && spaceList.size() > 0) {
            throw BizException.wrap(VenueBookingExceptionCode.SP_NOT_DELL);
        }
        SpaceCategory spaceCategory = new SpaceCategory();
        spaceCategory.setId(id);
        spaceCategory.setIsDeleted(1);
        Boolean del = this.updateById(spaceCategory);
        List<SpaceCategory> list= this.list(new QueryWrapper<SpaceCategory>().lambda()
                .eq(SpaceCategory::getIsDeleted, BusinessConstant.DELETE_NO)
                .eq(Objects.nonNull(id), SpaceCategory::getParentId, id));
        //查询分类下的二级
        if(Objects.nonNull(list) && list.size()>0){
            list.forEach((s)->{
                List<Space> spaces = getSpaceList(s.getId());
                if (Objects.nonNull(spaces) && spaces.size() > 0) {
                    throw BizException.wrap(VenueBookingExceptionCode.SP_NOT_DELL);
                }
                spaceCategory.setId(s.getId());
                spaceCategory.setIsDeleted(1);
                this.updateById(spaceCategory);
            });
        }

        if (Boolean.TRUE.equals(del)) {
            log.info("SpaceCategoryServiceImpl +++++ delSpaceCategoryInfoById -》》》》 删除展厅分类成功");
        }
        return del;
    }

    private List<Space>  getSpaceList(Long id){
        QueryWrapper<Space> queryWrapper = new QueryWrapper<>();
        queryWrapper.lambda()
                .eq(Objects.nonNull(id),
                        Space::getSpaceCategoryId, id)
                .eq(Space::getIsDeleted, BusinessConstant.DELETE_NO);
        List<Space> spaceList = spaceMapper.selectList(queryWrapper);
        return spaceList;
    }


}
